package com.jason.config;

import com.jason.core.wilddog.rest.handler.WilddogRestResponseErrorHandler;
import com.jason.core.wilddog.rest.interceptor.WilddogRestClientHttpRequestLoggerInterceptor;
import org.apache.http.client.HttpClient;
import org.apache.http.conn.ConnectTimeoutException;
import org.apache.http.impl.client.HttpClientBuilder;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.impl.conn.PoolingHttpClientConnectionManager;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.http.client.ClientHttpRequestFactory;
import org.springframework.http.client.ClientHttpRequestInterceptor;
import org.springframework.http.client.HttpComponentsClientHttpRequestFactory;
import org.springframework.web.client.RestTemplate;

import java.io.IOException;
import java.net.SocketTimeoutException;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;

/**
 * @author he peng
 * @create 2017/12/21 17:29
 * @see
 */

@Configuration
public class RestTemplateConfig {

    @Bean
    public RestTemplate restTemplate(ClientHttpRequestFactory requestFactory) {
        RestTemplate restTemplate = new RestTemplate(requestFactory);
        restTemplate.setErrorHandler(new WilddogRestResponseErrorHandler());
        List<ClientHttpRequestInterceptor> interceptors = new ArrayList<>(1);
        interceptors.add(new WilddogRestClientHttpRequestLoggerInterceptor());
        restTemplate.setInterceptors(interceptors);
        return restTemplate;
    }

//    @Bean
//    public ClientHttpRequestFactory requestFactory() {
//        SimpleClientHttpRequestFactory requestFactory = new SimpleClientHttpRequestFactory();
//        requestFactory.setConnectTimeout(3000);
//        requestFactory.setReadTimeout(3000);
//        return requestFactory;
//    }

    @Bean
    public ClientHttpRequestFactory httpComponentsClientHttpRequestFactory() {

        PoolingHttpClientConnectionManager pollingConnectionManager = new PoolingHttpClientConnectionManager();
        pollingConnectionManager.setMaxTotal(1000);
        pollingConnectionManager.setDefaultMaxPerRoute(1000);

        HttpClientBuilder httpClientBuilder = HttpClients.custom();
        httpClientBuilder.setConnectionManager(pollingConnectionManager);


        Set<Class<? extends IOException>> clazzes = new HashSet<>();
        clazzes.add(SocketTimeoutException.class);
        WilddogApiHttpRequestRetryHandler wilddogApiHttpRequestRetryHandler = new WilddogApiHttpRequestRetryHandler(3, true, clazzes);

        httpClientBuilder.setRetryHandler(wilddogApiHttpRequestRetryHandler);

        HttpClient httpClient = httpClientBuilder.build();
        HttpComponentsClientHttpRequestFactory clientHttpRequestFactory = new HttpComponentsClientHttpRequestFactory(httpClient);
        clientHttpRequestFactory.setConnectTimeout(5);
        clientHttpRequestFactory.setReadTimeout(5);
        clientHttpRequestFactory.setConnectionRequestTimeout(200);
        clientHttpRequestFactory.setBufferRequestBody(true);
        return clientHttpRequestFactory;
    }
}
